package me.minecraft.mod.cobblemonbukkitevent.mixin;

import com.cobblemon.mod.common.Cobblemon;
import com.cobblemon.mod.common.api.battles.model.PokemonBattle;
import com.cobblemon.mod.common.api.battles.model.actor.BattleActor;
import com.cobblemon.mod.common.battles.ActiveBattlePokemon;
import com.cobblemon.mod.common.battles.interpreter.instructions.SwitchInstruction;
import com.cobblemon.mod.common.battles.pokemon.BattlePokemon;
import kotlin.Pair;
import me.minecraft.mod.cobblemonbukkitevent.bukkit.EventFactory;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.Inject;
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;

/**
 * @author langle__
 * @version 1.0
 */
@Mixin(value = SwitchInstruction.class, remap = false)
public class SwitchInstructionMixin {

    @Inject(method = {"invoke"}, at = {@At("HEAD")}, remap = false)
    private void onSwitchStart(PokemonBattle battle, CallbackInfo ci) {
        SwitchInstruction instruction = (SwitchInstruction) (Object) this;
        BattleActor actor = instruction.getBattleActor();
        Pair<String, String> pnxAndUuid = instruction.getPublicMessage().pnxAndUuid(0);
        if (pnxAndUuid == null) {
            Cobblemon.LOGGER.info("pnxAndUuid is null");
            return;
        }
        Pair<BattleActor, ActiveBattlePokemon> actorAndSlot = battle.getActorAndActiveSlotFromPNX(pnxAndUuid.getFirst());
        ActiveBattlePokemon activePokemon = actorAndSlot.getSecond();
        BattlePokemon oldPokemon = activePokemon.getBattlePokemon();
        BattlePokemon newPokemon = instruction.getPublicMessage().battlePokemon(0, battle);
        if (oldPokemon != null && newPokemon != null && !oldPokemon.equals(newPokemon)) {
            EventFactory.callPokemonSwitchStartEvent(battle, actor, oldPokemon, newPokemon);
            Cobblemon.LOGGER.info("Pokemon switch start event triggered");
        }
    }

    @Inject(method = {"invoke"}, at = {@At("RETURN")}, remap = false)
    private void onSwitchEnd(PokemonBattle battle, CallbackInfo ci) {
        SwitchInstruction instruction = (SwitchInstruction) (Object) this;
        BattleActor actor = instruction.getBattleActor();
        Pair<String, String> pnxAndUuid = instruction.getPublicMessage().pnxAndUuid(0);
        if (pnxAndUuid == null) {
            Cobblemon.LOGGER.info("pnxAndUuid is null");
            return;
        }
        Pair<BattleActor, ActiveBattlePokemon> actorAndSlot = battle.getActorAndActiveSlotFromPNX(pnxAndUuid.getFirst());
        ActiveBattlePokemon activePokemon = actorAndSlot.getSecond();
        BattlePokemon oldPokemon = activePokemon.getBattlePokemon();
        BattlePokemon newPokemon = instruction.getPublicMessage().battlePokemon(0, battle);
        if (oldPokemon != null && newPokemon != null && !oldPokemon.equals(newPokemon)) {
            EventFactory.callPokemonSwitchEndEvent(battle, actor, oldPokemon, newPokemon);
            Cobblemon.LOGGER.info("Pokemon switch end event triggered");
        }
    }

}
